/* ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
   Module Name          : com.yaodian100.ec.product.remote.RemoteProductServiceImpl
   Module Description   :

   Date Created      : 2010/2/1
   Original Author   : ellen.li
   Team              : yaodian100
   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
   MODIFICATION HISTORY
   ------------------------------------------------------------------------------
   Date Modified       Modified by       Comments
   ------------------------------------------------------------------------------
   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++*/
package com.yaodian100.ec.product.remote;

import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;

import javax.annotation.Resource;

import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.core.JdbcTemplate;

import com.yaodian100.core.admin.service.UserService;
import com.yaodian100.core.batch.service.BatchJobService;
import com.yaodian100.core.common.dao.impl.CommonCriteria;
import com.yaodian100.core.mail.entity.Mail;
import com.yaodian100.core.mail.service.MailService;
import com.yaodian100.core.template.service.TemplateService;
import com.yaodian100.core.thread.service.ThreadService;
import com.yaodian100.ec.category.entity.Category;
import com.yaodian100.ec.category.service.CategoryService;
import com.yaodian100.ec.common.EnvParameters;
import com.yaodian100.ec.product.batch.BuildProductJob;
import com.yaodian100.ec.product.entity.AddOnProduct;
import com.yaodian100.ec.product.entity.Product;
import com.yaodian100.ec.product.service.Product2Service;
import com.yaodian100.ec.product.service.ProductService;
import com.yaodian100.ec.shelf.entity.ViewShelf;

/**
 * @author ellen.li
 * 
 */
public class RemoteProductServiceImpl implements RemoteProductService {
	private static Logger logger = LoggerFactory.getLogger(RemoteProductServiceImpl.class);
	@Autowired
	private ProductService productService;
	@Resource(name = "userService")
	private UserService userService;
	@Autowired
	private Product2Service product2Service;
	@Autowired
	private BatchJobService batchJobService;
	@Resource
	private MailService mailService;
	@Autowired
	private TemplateService velocityService;
	@Resource
	private EnvParameters envParameters;
	@Autowired
	private CategoryService categoryService;
	@Autowired
	private ThreadService threadService;
	@Autowired
	private JdbcTemplate jdbcTemplate;

	@Override
	public String updateProductCost(String productId, BigDecimal cost) {
		try {
			Product p = productService.get(productId);
			if (p == null) {
				return "[updateProductcCost]查无此商品:" + productId;
			}

			p.setProductCost(cost);
			productService.updateNoSync(p);
			return "true";
		} catch (Exception e) {
			logger.error("[updateProductcCost]err:", e);
			return "[updateProductcCost]err:" + e.getMessage();
		}
	}

	@Override
	public String updateProductCostArray(String[] productId, BigDecimal[] cost) {
		return productService.updateProductCostArray(productId, cost);
	}

	@Override
	public String updatePreOrderProduct(int count) {
		try {
			CommonCriteria cc = new CommonCriteria();
			cc.addEq("productType", 1);
			cc.addLe("expectShipDate", new Date());

			List<Product> products = productService.getList(0, count, cc, null);
			for (Product product : products) {
				product.setProductType(0);

				product.setProductMemo(StringUtils.defaultString(product.getProductMemo()) + " 本商品已於 "
						+ new SimpleDateFormat("yyyy-MM-dd HH:mm").format(new Date()) + " 由系統自動異動(預購 -> 一般商品)");
				productService.save(product);

				// logger.info(product.getProductId() + "," + product.getExpectShipDate());
			}

			return "true";
		} catch (Exception e) {
			// TODO: handle exception
			return "[updatePreOrderProduct]err:" + e.getMessage();
		}

	}

	@Override
	public String updateAddOnProductStatus(int count) {
		try {
			CommonCriteria cc = new CommonCriteria();
			cc.addLe("endDate", new Date());
			cc.addEq("isEnable", "Y");
			List<AddOnProduct> addOnProducts = productService.getAddOnProductList(0, -1, cc, null);
			for (AddOnProduct addOnProduct : addOnProducts) {
				addOnProduct.setIsEnable("N");
				productService.saveAddOnProduct(addOnProduct);
			}
			return "true";
		} catch (Exception e) {
			return "[updateAddOnProductStatus]err:" + e.getMessage();
		}
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see com.yaodian100.ec.product.remote.RemoteProductService#syncIsScmToBO(java.util.Date)
	 */
	@Override
	public String syncProductIsScm(int count) {
		return "true";
	}

	@Override
	public String sendCodLimitReport(String date) {
		try {
			List<ViewShelf> shelf = product2Service.getCODLimitProduct("N", "N", "50");
			Map<String, Object> contentMap = new HashMap<String, Object>();
			contentMap.put("shelfs", shelf);
			Mail mail = velocityService.formatToMail("product.codLimit", contentMap);
			mail.setFrom(envParameters.getEmailFromSystem());
			mail.setTo("codreport@yaodian100.com");
			mailService.save(mail);
		} catch (Exception e) {
			return "[sendCodLimitReport]err:" + e.getMessage();
		}

		return "true";
	}

	@Override
	public boolean checkAll() {
		List<Category> rootCategories = categoryService.getChild(Long.parseLong("0"));
		buildProps(rootCategories);
		return true;
	}

	public boolean buildProps(List<Category> rootCategories) {
		List<Map<String, Object>> rootProds = null;
		if (rootCategories != null) {
			for (Category prod : rootCategories) {
				rootProds = getProducts(prod.getCategoryPath());
				BuildProductJob build = new BuildProductJob(rootProds, prod.getCategoryPath(), rootCategories);
				build.setEnvParameters(envParameters);
				build.setMailService(mailService);
				build.setUserService(userService);
				build.setVelocityService(velocityService);
				threadService.executeInBackground(build);
			}
		}
		return true;
	}

	private List<Map<String, Object>> getProducts(String rootId) {
		List<Map<String, Object>> products = null;
		String value = rootId + "/%";
		try {
			StringBuffer sb = new StringBuffer();
			sb.append("select a.main_category_Id ,a.main_category_path,a.product_id, a.PRODUCT_NAME,a.is_delete,a.is_scm,b.SPECIFICATION_NAME,b.specification_id, (c.available_inventory-c.SOLD_INVENTORY+c.CANCEL_INVENTORY) SALESINV,b.safe_inventory");
			sb.append(" from ec_product_main a,ec_specification b,ec_specification_inventory c");
			sb.append(" where  a.main_category_path like ? and a.product_id=b.product_id and c.spec_id=b.specification_id and a.is_delete!='Y' and a.product_type!='6' and b.is_delete='N' and (c.available_inventory-c.SOLD_INVENTORY+c.CANCEL_INVENTORY)<b.safe_inventory");
			sb.append(" order by a.main_category_path,a.product_id,b.SPECIFICATION_NAME");
			products = jdbcTemplate.queryForList(sb.toString(), value);
		} catch (Exception e) {
			logger.error(e.toString());
		}
		return products;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see com.yaodian100.ec.product.remote.RemoteProductService#checkInventory(java.lang.String, java.lang.String,
	 * java.lang.String)
	 */
	@Override
	public String[] checkInventory(String supplierId, String productIdRangeFrom, String productIdRangeEnd) {
		String[] inventoryInfo = null;
		try {
			StringBuffer sb = new StringBuffer();
			sb.append("select a.product_id as productId,a.spec_id as specId ,a.available_inventory+a.cancel_inventory-a.sold_inventory as inventory ");
			sb.append(" from ec_specification_inventory a, ec_product_main b");
			sb.append(" where b.product_id = a.product_id and b.supplier_id = ? and");
			sb.append(" b.product_id >= ? and b.product_id <= ? ");
			List<Map<String, Object>> result = jdbcTemplate.queryForList(sb.toString(), supplierId, productIdRangeFrom,
					productIdRangeEnd);

			inventoryInfo = new String[result.size()];
			int count = 0;
			for (Map<String, Object> row : result) {
				StringBuffer rowString = new StringBuffer().append(row.get("PRODUCTID")).append(",").append(row.get("SPECID"))
						.append(",").append(row.get("INVENTORY"));
				inventoryInfo[count] = rowString.toString();
				count++;
			}

		} catch (Exception e) {
			e.printStackTrace();
		}
		return inventoryInfo;
	}

	@Override
	public String checkInventorySet(Set<String> specIds) {
		StringBuffer inventoryResult = new StringBuffer();
		try {
			StringBuffer sb = new StringBuffer();
			sb.append("select si.spec_id as specId ,si.available_inventory+si.cancel_inventory-si.sold_inventory as inventory ");
			sb.append(" from ec_specification_inventory si");
			sb.append(" where si.spec_id = ?");
			for (String specId : specIds) {
				List<Map<String, Object>> result = jdbcTemplate.queryForList(sb.toString(), Long.valueOf(specId));
				String inventoryInfo;
				if (result != null && result.size() > 0) {
					inventoryInfo = result.get(0).get("INVENTORY").toString();
				} else {
					inventoryInfo = "0";
				}
				inventoryResult.append(specId).append(":").append(inventoryInfo).append(",");
			}
		} catch (Exception e) {
			e.printStackTrace();
		}
		return inventoryResult.toString();
	}
}